package com.ldk.run;

import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import com.ldk.Runnable.DataDealRunnable2;
import com.ldk.util.FileOpt;
import com.ldk.util.StringOpt;
import com.ldk.util.ZipUtil;

public class WorkImpl implements Work  {
	private String targetHead;
	private String zipPath;
	private List<String> instructions;
	private List<String> allFileName;
	private List<String> changeFile = new ArrayList<String>();
	private ExecutorService exec = Executors.newFixedThreadPool(10);
	
	public WorkImpl(){}
	
	/**
	 * 处理逻辑
	 * 1.获取目标项目下的所有可比对文件			---getAllFile()
	 * 2.根据得到的文件列表进行文件比对			---diff()
	 * 3.构建项目							---build()
	 * 4.附加逻辑
	 */
	public void work(String targetHead,List<String> instructions){
		this.targetHead = targetHead;
		this.zipPath = targetHead+"_"+StringOpt.stampToDate();
		this.instructions = instructions;
		System.out.println("获取全部文件列表...");
		long zStart = System.currentTimeMillis();
		getAllFile();
		System.out.println("获取文件结束...耗时:"+(System.currentTimeMillis()-zStart)+"ms");
		long start = System.currentTimeMillis();
		System.out.println("开始比对文件...");
		diff();
		System.out.println("比对文件结束...耗时:"+(System.currentTimeMillis()-start)+"ms");
		
		start = System.currentTimeMillis();
		System.out.println("开始构建web项目...");
		build();
		write();
		System.out.println("构建web项目结束...耗时:"+(System.currentTimeMillis()-start)+"ms");
//		start = System.currentTimeMillis();
//		System.out.println("开始压缩web项目...");
//		zipFile();
//		System.out.println("压缩web项目结束...耗时:"+(System.currentTimeMillis()-start)+"ms");
		System.out.println("总耗时:"+(System.currentTimeMillis()-zStart)+"ms");
		exec.shutdown();
	}
	
	/**
	 * 将项目下的所有文件列出
	 * 剔除:
	 * 1.以.开头的文件
	 * 2.classes下的文件
	 */
	public void getAllFile(){
		allFileName = FileOpt.getAllFile(targetHead);
	}
	
	/**
	 * 比对文件差异
	 * 单线程操作
	 */
	public void diff(){
		int length = allFileName.size();
		for(int i = 0;i<length;i+=10){
			//10个分一个数据块
			int count = i+9>=length?length-1:i+9;
			exec.execute(new DataDealRunnable2(allFileName.subList(i, count+1), targetHead,changeFile));
		}
		exec.shutdown(); 
		while (true) { 
			if (exec.isTerminated()) { 
				break;
			}
			try {
				Thread.sleep(200);
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
	
	/**
	 * 构建web项目
	 */
	public void build(){
		List<String> diffFileName = changeFile;
		if(zipPath!=null && zipPath!=""){
			for(int i=0;i<diffFileName.size();i++){
				String fileName = diffFileName.get(i);
				String addPath = null;
				String s = fileName.substring(StringOpt.getCharacterPosition(fileName, "/", 1));
				if(fileName.endsWith(".xml") || fileName.endsWith(".properties")){
					addPath = "/WebRoot/WEB-INF/classes"+s;
				}else if(fileName.endsWith(".java")){
					s = s.replaceAll("java", "class");
					addPath = "/WebRoot/WEB-INF/classes"+s;
				}else if(fileName.startsWith("WebRoot")){
					addPath = s;
				}
				if(addPath!=null)
				{
					FileOpt.copyFile(targetHead+"/"+fileName, zipPath+addPath);
				}
			}
		}
	}
	
	/**
	 * 生成说明文件
	 */
	public void write(){
		try {
			File f = new File(zipPath+"/说明.txt");
			if(!f.exists()){
				f.createNewFile();
			}
			FileOpt.writeFileContent(zipPath+"/说明.txt","说明:");
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	/**
	 * 将更新文件压缩
	 */
	public void zipFile(){
		List files = new ArrayList<File>();
		File zipParent = new File(zipPath);
		File[] zipChildrens = zipParent.listFiles();
		for(int i = 0;i<zipChildrens.length;i++){
			files.add(zipChildrens[i]);
		}
		ZipUtil.zipFile(zipPath+".zip", files);
	}

	public String getTargetHead() {
		return targetHead;
	}

	public List<String> getInstructions() {
		return instructions;
	}

	public void setTargetHead(String targetHead) {
		this.targetHead = targetHead;
	}

	public void setInstructions(List<String> instructions) {
		this.instructions = instructions;
	}
	
}
